package com.example.demo;

import com.alibaba.druid.pool.DruidDataSource;
import com.alibaba.druid.pool.DruidDataSourceFactory;
import org.I0Itec.zkclient.IZkDataListener;
import org.I0Itec.zkclient.ZkClient;

import javax.sql.DataSource;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.HashMap;
import java.util.Map;
import java.util.Random;

public class DynamicDataSourceUtils {

    public static HashMap<String,String> config = new HashMap<>();
    private static ZkClient zkclient = new ZkClient("linux123:2181");
    private static String configPath="/sqlConfig";
    private static DruidDataSource druidDataSource = new DruidDataSource();
    private static  final String[] USERNAMES = {"hive","testuser1"};
    private static Random random = new Random();


    static {
        config.put("driverClassName","com.mysql.cj.jdbc.Driver");
        config.put("url","jdbc:mysql://linux123:3306/?characterEncoding=UTF-8");
        config.put("username","hive");
        config.put("password","12345678");
    }

    //设置数据源
    public static void initDataSource(Map<String,String> config) {
        try {
            DruidDataSourceFactory.config(druidDataSource,config);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
    //设置zk路径/sqlConfig下内容的值
    public static void setZk(HashMap<String, String> config) {
        if (zkclient.exists(configPath)) {
            zkclient.writeData(configPath,config);
        }else {
            zkclient.createPersistent(configPath,config);
        }
    }

    public static void randomConfig() {
        String username = USERNAMES[random.nextInt(2)];
        config.put("username", username);
        //config.remove("driverClassName");
        setZk(config);
    }


    //设置监听器，当“/sqlConfig”发生变化，设置对应值到config
    public static void dynamicSetDatasource(){

        zkclient.subscribeDataChanges(configPath, new IZkDataListener() {
            @Override
            public void handleDataChange(String dataPath, Object data) throws Exception {
                assert data instanceof Map;
                //关闭数据源
                druidDataSource.restart();
                //取出data设置DruidDataSource
                DruidDataSourceFactory.config(druidDataSource,(Map<String,String>) data);
                testConnection(druidDataSource);
            }

            @Override
            public void handleDataDeleted(String dataPath) throws Exception {

            }
        });
    }


    /*获取dataSource打印当前用户名*/
    public static void testConnection(DataSource dataSource) throws SQLException {
        try (Connection connection = dataSource.getConnection()) {
            assert connection!=null;
            ResultSet resultSet = connection.prepareStatement("select user()").executeQuery();
            while(resultSet.next()) {
                System.out.println("当前用户名：" + resultSet.getString(1));
            }
        }
    }
}
